package com.thornbird.vehiclerecycling.controller;

import com.thornbird.vehiclerecycling.config.OAuth2LoginConfig;
import com.thornbird.vehiclerecycling.model.response.Result;
import com.thornbird.vehiclerecycling.util.ResultUtil;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.web.savedrequest.HttpSessionRequestCache;
import org.springframework.security.web.savedrequest.RequestCache;
import org.springframework.security.web.savedrequest.SavedRequest;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.net.URI;

@Controller
@Configuration
public class OAuth2Controller {

    public final static String ORIGINAL_URL = "X-ORIGINAL-URL";

    public static final String API_PREFIX = "api";

    @Value("${app.default-sso-source}")
    private String defaultSsoSource;

    private RequestCache requestCache = new HttpSessionRequestCache();

    @RequestMapping(method = RequestMethod.GET, value = "/login")
    public String login() {
        return "redirect:/login/oauth2";
    }

    @RequestMapping(method = RequestMethod.GET, value = "/login/oauth2")
    public String loginOAuth2(HttpServletRequest request, HttpServletResponse response) {
        HttpSession session = request.getSession(false);
        SavedRequest savedRequest = requestCache.getRequest(request, response);
        String url = null;
        if (session != null) {
            session.setAttribute(OAuth2LoginConfig.CURRENT_USER, null);
        }
        if (savedRequest != null) {
            url = savedRequest.getRedirectUrl();
        } else {
            String originalUrl = request.getHeader(ORIGINAL_URL);
            if (originalUrl != null && !originalUrl.isEmpty()) {
                url = originalUrl;
            }
        }
        if (url != null && isApiRequest(url)) {
            return "redirect:/login/unauthorized";
        }
        return "redirect:/login/oauth2/authorization/" + defaultSsoSource;
    }

    @RequestMapping(method = RequestMethod.GET, value = "/login/oauth2/exit")
    public String loginOAuth2Exit() {
        return "error/401";
    }

    @ResponseBody
    @RequestMapping(method = RequestMethod.GET, value = "/login/unauthorized")
    public Result<?> unauthorized() {
        return ResultUtil.unauthorizedError();
    }

    private static boolean isApiRequest(String url) {
        String path = URI.create(url).getPath();
        String[] parts = path.split("/");
        if (parts.length > 1 && parts[1].toLowerCase().equals(API_PREFIX)) {
            return true;
        }
        return false;
    }

}
